﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using TA.JSON;
using System.ComponentModel;
using TA.Turbo.Controls;

namespace TA.Turbo
{
	/// <summary>
	/// Base class for all markup templates.
	/// </summary>
	public abstract class BaseMarkupTemplate : IMarkupTemplate, IJsonSerializable
	{
		#region PUBLIC
		#region INIT
		/// <summary>
		/// Ctor.
		/// </summary>
		/// <param name="name"></param>
		public BaseMarkupTemplate(string name)
		{
			this.Name = name;

		}
		#endregion
		#region PROPS
		/// <summary>
		/// Gets or sets the name of this template.
		/// </summary>
		[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
		[Browsable(false)]
		public string Name { get; set; }
		/// <summary>
		/// Gets the HTML markup of this template.
		/// </summary>
		[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
		[Browsable(false)]
		public string Markup
		{
			get
			{
				this.PrepareMarkupAndScript();
				return this._markup;
			}
		}
		/// <summary>
		/// Gets the client script needed to initialize this template in the browser.
		/// </summary>
		[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
		[Browsable(false)]
		public string Script
		{
			get
			{
				this.PrepareMarkupAndScript();
				return this._script;
			}
		}
		#endregion
		#region METHODS
		///// <summary>
		///// Adds markup and script attributes for client-side consumption.
		///// </summary>
		///// <param name="writer"></param>
		//public void AddAttributes(System.Web.UI.HtmlTextWriter writer)
		//{
		//  if (TPage.Current != null)
		//  {
		//    if (TPage.Current.JavaScript != false)
		//    {
		//      writer.AddAttribute(this.Name + "-Markup", this.Markup);
		//      writer.AddAttribute(this.Name + "-Script", this.Script);
		//    }
		//  }
		//}
		#region JSON
		/// <summary>
		/// IsDirty.
		/// </summary>
		[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
		[Browsable(false)]
		public bool IsDirty
		{
			get { return true; }
		}
		/// <summary>
		/// Serialize.
		/// </summary>
		/// <param name="jw"></param>
		public void Serialize(JsonWriter jw)
		{
			this.SerializeObject(jw);
		}
		/// <summary>
		/// SerializeContents.
		/// </summary>
		/// <param name="jw"></param>
		public virtual void SerializeContents(JsonWriter jw)
		{
			jw.PropertyName("N");
			jw.Value(this.Name);

			jw.PropertyName("M");
			jw.Value(this.Markup);

			jw.PropertyName("S");
			jw.Value(this.Script);
		}
		#endregion
		#endregion
		#endregion
		#region INTERNAL
		#region VARS
		string _markup, _script;
		bool _done = false;
		#endregion
		#region PROPS
		/// <summary>
		/// Sets the HTML markup during preparation.
		/// </summary>
		protected void SetMarkup(string value)
		{
			this._markup = value;
		}
		/// <summary>
		/// Sets the initialization script during preparation.
		/// </summary>
		protected void SetScript(string value)
		{
			this._script = value;
		}
		#endregion
		#region METHODS
		/// <summary>
		/// Ensures that HTML markup and initialization script are ready.
		/// </summary>
		void EnsureMarkupAndScript()
		{
			if (this._done) return;

			this.PrepareMarkupAndScript();

			this._done = true;
		}
		/// <summary>
		/// When implemented, prepares the HTML markup and the initialization script for this template.
		/// </summary>
		protected abstract void PrepareMarkupAndScript();
		#endregion
		#endregion
	}
}
